package downloader

import (
	"fmt"
	"sync"

	"webpagedown3/internal/utils"
	"webpagedown3/pkg/task"
)

type Config struct {
	Concurrency int
	MaxDepth    int
	OutputDir   string
	MaxRetries  int
	Urls        []string
	Resources   bool
}

var wg sync.WaitGroup

func NewConfig(concurrency int, maxDepth int, outputDir string, maxRetries int, urls []string, resources bool) *Config {
	return &Config{
		Concurrency: concurrency,
		MaxDepth:    maxDepth,
		OutputDir:   outputDir,
		MaxRetries:  maxRetries,
		Urls:        urls,
		Resources:   resources,
	}
}

func Download(config *Config, downloadedURLs *sync.Map) error {
	tasks, err := task.InitTasks(config.Urls, config.OutputDir, config.MaxRetries, downloadedURLs)
	if err != nil {
		fmt.Printf("初始化下载任务失败: %v\n", err)
		return err
	}

	// 创建工作池
	var taskCh = make(chan *task.DownloadTask, len(tasks)*10) // 增大缓冲区以容纳资源下载任务

	// 在启动工作协程前初始化
	var taskMutex sync.Mutex // 保护计数器的互斥锁
	activeTaskCount := int32(len(tasks))

	// 启动工作协程
	for i := 0; i < config.Concurrency; i++ {
		wg.Add(1)
		go func() {
			defer wg.Done()
			for downloadtask := range taskCh {
				// fmt.Printf("Worker: downloadtask.DownloadedURL = %v\n", downloadtask.DownloadedURL)
				// if _, loaded := downloadtask.DownloadedURL.LoadOrStore(downloadtask.URL, true); loaded {
				// 	atomic.AddInt32(&activeTaskCount, -1)
				// 	continue
				// }
				err := utils.DownloadWithRetry(downloadtask, config.MaxDepth, config.Resources, taskCh, &activeTaskCount, &taskMutex)
				if err != nil {
					fmt.Printf("下载失败: %v\n", err)
				}
			}
		}()
	}

	// 发送任务到通道
	for _, downloadtask := range tasks {
		taskCh <- downloadtask
	}

	// 等待所有下载完成
	wg.Wait()

	// 等待通道关闭
	for range taskCh {
	}

	fmt.Println("所有下载任务已完成")
	return nil
}
